﻿using System;
using System.Collections.Generic;
using System.Text;
using System.Text.RegularExpressions;

namespace TidyBlog.Data
{
    /// <summary>
    /// SELECT命令生成类
    /// </summary>
    public class SelectCommand : Command
    {
        /// <summary>
        /// 查询列
        /// </summary>
        public List<string> SelectColumns
        {
            get;
            protected set;
        }
        /// <summary>
        /// 排序列
        /// </summary>
        public List<SortColumn> SortColumns
        {
            get;
            protected set;
        }
        /// <summary>
        /// 查询数量，0为不限制数量
        /// </summary>
        protected int Amount;

        /// <summary>
        /// 匹配包含函数的列
        /// </summary>
        protected static readonly Regex IsFunctionColumn = new Regex(@"\((.+?)\)");


        public SelectCommand(string table)
            : base(table)
        {

        }

        public SelectCommand(string[] tables)
            : base(tables)
        {

        }


        /// <summary>
        /// 指定查询的列
        /// </summary>
        /// <param name="column">列</param>
        /// <returns>当前命令</returns>
        public SelectCommand Select(string column)
        {
            if (column != null)
            {
                SelectColumns = new List<string>();
                SelectColumns.Add(column);
            }

            return this;
        }
        /// <summary>
        /// 指定查询的列
        /// </summary>
        /// <param name="columns">列</param>
        /// <returns>当前命令</returns>
        public SelectCommand Select(IEnumerable<string> columns)
        {
            if (columns != null)
            {
                SelectColumns = new List<string>(columns);
            }

            return this;
        }

        /// <summary>
        /// 指定排序列
        /// </summary>
        /// <param name="sortColumn">排序列</param>
        /// <returns>当前命令</returns>
        public SelectCommand OrderBy(SortColumn sortColumn)
        {
            if (sortColumn != null)
            {
                SortColumns = new List<SortColumn>();
                SortColumns.Add(sortColumn);
            }

            return this;
        }

        /// <summary>
        /// 指定排序列
        /// </summary>
        /// <param name="sortColumns">排序列</param>
        /// <returns>当前命令</returns>
        public SelectCommand OrderBy(IEnumerable<SortColumn> sortColumns)
        {
            if (sortColumns != null)
            {
                SortColumns = new List<SortColumn>(sortColumns);
            }

            return this;
        }

        /// <summary>
        /// 获取ORDER BY子句字符串
        /// </summary>
        /// <returns>ORDER BY子句字符串</returns>
        protected string GetOrderByString()
        {
            if (SortColumns == null || SortColumns.Count == 0)
            {
                return String.Empty;
            }

            var result = new StringBuilder();

            foreach (var sortColumn in SortColumns)
            {
                if (result.Length > 0)
                {
                    result.Append(",");
                }

                result.Append(sortColumn.Column);
                result.Append(" ");
                result.Append(sortColumn.OrderWay.ToString());
            }
            if (result.Length > 0)
            {
                result.Insert(0, " ORDER BY ");
            }

            return result.ToString();
        }

        /// <summary>
        /// 指定返回的记录数
        /// </summary>
        /// <param name="amount">记录数</param>
        /// <returns>当前命令</returns>
        public SelectCommand Top(int amount)
        {
            Amount = amount;

            return this;
        }

        /// <summary>
        /// 获取查询列字符串
        /// </summary>
        /// <returns>查询列字符串</returns>
        protected string GetSelectColumnString()
        {
            var result = new StringBuilder();
            var quote = DbHelper.Provider.QuoteSymbol;

            foreach (var column in SelectColumns)
            {
                if (result.Length > 0)
                {
                    result.Append(",");
                }

                if (IsFunctionColumn.IsMatch(column))
                {
                    result.Append(IsFunctionColumn.Replace(column, m =>
                    {
                        var val = m.Groups[1].Value;
                        return "(" + (val == "*" ? val : String.Format(quote, val)) + ")";
                    }));
                }
                else
                {
                    result.Append(column == "*" ? column : String.Format(quote, column));
                }
            }

            return result.ToString();
        }

        /// <summary>
        /// 生成SQL命令字符串
        /// </summary>
        /// <returns>SQL命令字符串</returns>
        public override string ToString()
        {
            string template;
            var formatParams = new List<string>();
            formatParams.Add(GetTableString());
            formatParams.Add(GetSelectColumnString());
            formatParams.Add(GetWhereString());
            formatParams.Add(GetOrderByString());

            if (Amount > 0)
            {
                template = "READ_TOP_N";
                formatParams.Add(Amount.ToString());
            }
            else
            {
                template = "READ";
            }

            return String.Format(DbHelper.Provider.GetCmdTemplate(template), formatParams.ToArray());
        }
    }
}
